package com.jinly.ryder.manage.service.impl;

import com.baomidou.mybatisplus.core.conditions.Wrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.jinly.ryder.common.error.SystemErrorType;
import com.jinly.ryder.common.service.SettingItemService;
import com.jinly.ryder.manage.dao.AppInfoMapper;
import com.jinly.ryder.manage.dao.entity.AppInfoDO;
import com.jinly.ryder.manage.service.AppInfoService;
import com.jinly.ryder.manage.service.DeployGroupService;
import com.jinly.ryder.manage.service.mapping.AppInfoMapping;
import com.jinly.ryder.manage.service.model.AppInfo;
import com.jinly.ryder.manage.service.model.AppInfoSaveEvent;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.context.ApplicationEventPublisher;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;

@Slf4j
@Service
@RequiredArgsConstructor
public class AppInfoServiceImpl implements AppInfoService {

    private final AppInfoMapper appInfoMapper;
    private final AppInfoMapping appInfoMapping;
    private final DeployGroupService deployGroupService;
    private final SettingItemService settingItemService;
    private final ApplicationEventPublisher eventPublisher;

    @Override
    public List<AppInfo> allList() {
        List<AppInfo> appInfoList = appInfoMapping.toModelList(appInfoMapper.selectList(null));
        return appInfoList;
    }

    @Override
    public Page<AppInfo> queryAppPage(Page page, AppInfo query) {
        Wrapper<AppInfoDO> queryWrapper = new QueryWrapper<AppInfoDO>().lambda()
                .like(query.getAppName() != null, AppInfoDO::getAppName, query.getAppName())
                .like(query.getAppShowName() != null, AppInfoDO::getAppShowName, query.getAppShowName());
        return appInfoMapping.toModelPage(appInfoMapper.selectPage(page, queryWrapper));
    }

    @Override
    public AppInfo getAppInfo(String appName) {
        Wrapper<AppInfoDO> queryWrapper = new QueryWrapper<AppInfoDO>().lambda()
                .eq(AppInfoDO::getAppName, appName);
        AppInfo appInfo = appInfoMapping.toModel(appInfoMapper.selectOne(queryWrapper));
        settingItemService.setSettingItem(appInfo);
        return appInfo;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void save(AppInfo appInfo) {
        if (appInfo.getId() == null) {
            AppInfoDO appInfoDO = appInfoMapping.toEntity(appInfo);
            appInfoMapper.insert(appInfoDO);
            appInfo.setId(appInfoDO.getId());
        } else {
            appInfoMapper.updateById(appInfoMapping.toEntity(appInfo));
        }
        settingItemService.saveSettingItem(appInfo);
        try {
            eventPublisher.publishEvent(new AppInfoSaveEvent(appInfo));
        } catch (Exception e) {
            log.error("publish AppInfoSaveEvent err", e);
        }

    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void deleteApp(String appName) {
        AppInfo appInfo = getAppInfo(appName);
        if (appInfo == null) return;
        if (deployGroupService.list(appName).size() != 0) {
            SystemErrorType.BAD_REQUEST.throwError("请先删除该应用的分组");
        }
        appInfoMapper.deleteById(appInfo.getId());
        log.info("删除应用{}成功", appName);
    }
}
